package com.cpd.blog.manager.manager.impl;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.cpd.blog.common.constant.Constant;
import com.cpd.blog.common.constant.StatusCode;
import com.cpd.blog.common.utils.CheckUtil;
import com.cpd.blog.common.utils.LogUtil;
import com.cpd.blog.common.utils.PageUtil;
import com.cpd.blog.dto.Article.Archives;
import com.cpd.blog.dto.Article.ArticleRep;
import com.cpd.blog.dto.Article.TagVo;
import com.cpd.blog.dto.Page.PageParams;
import com.cpd.blog.entity.Article;
import com.cpd.blog.entity.ArticleBody;
import com.cpd.blog.entity.ArticleTag;
import com.cpd.blog.manager.manager.ArticleManager;
import com.cpd.blog.manager.mapper.ArticleBodyMapper;
import com.cpd.blog.manager.mapper.ArticleMapper;
import com.cpd.blog.manager.mapper.ArticleTagMapper;
import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Service;

import java.time.LocalDateTime;
import java.util.List;

/**
 * @Author: Copydown
 * @Date: 2022/04/30/2:30
 */

@Service
@RequiredArgsConstructor
public class ArticleManagerImpl implements ArticleManager {

    private final ArticleMapper articleMapper;

    private final ArticleBodyMapper articleBodyMapper;

    private final ArticleTagMapper articleTagMapper;

    @Override
    public boolean deleteArticleRelateById(Long articleId) {
        QueryWrapper<Article> articleWrapper = new QueryWrapper<>();
        QueryWrapper<ArticleBody> bodyWrapper = new QueryWrapper<>();
        QueryWrapper<ArticleTag> tagWrapper = new QueryWrapper<>();

        articleWrapper.lambda().eq(Article::getId, articleId);
        bodyWrapper.lambda().eq(ArticleBody::getArticleId, articleId);
        tagWrapper.lambda().eq(ArticleTag::getArticleId, articleId);

        if (articleMapper.delete(articleWrapper) != 1) {
            LogUtil.log(StatusCode.ARTICLE_SINGLE_DELETE_FAILED);
            return false;
        }
        LogUtil.log(StatusCode.ARTICLE_SINGLE_DELETE_SUCCESS);

        if (articleBodyMapper.delete(bodyWrapper) != 1) {
            LogUtil.log(StatusCode.ARTICLE_BODY_DELETE_FAILED);
            return false;
        }
        LogUtil.log(StatusCode.ARTICLE_BODY_DELETE_SUCCESS);

        if (articleTagMapper.delete(tagWrapper) < 0) {
            LogUtil.log(StatusCode.ARTICLE_TAG_DELETE_FAILED);
            return false;
        }
        LogUtil.log(StatusCode.ARTICLE_TAG_DELETE_SUCCESS);
        return true;
    }

    @Override
    public ArticleRep updateArticleWithRelate(Article article, ArticleBody articleBody, List<TagVo> tagList) {

        if (articleMapper.updateById(article) <= 0) {

        }
        UpdateWrapper<ArticleBody> bodyUpdateWrapper = new UpdateWrapper<>();
        bodyUpdateWrapper.lambda().eq(ArticleBody::getArticleId, article.getId());

        if (articleBodyMapper.update(articleBody, bodyUpdateWrapper) <= 0) {

        }
        QueryWrapper<ArticleTag> tagQueryWrapper = new QueryWrapper<>();
        tagQueryWrapper.lambda().eq(ArticleTag::getArticleId, article.getId());
        articleTagMapper.delete(tagQueryWrapper);

        for (TagVo tag : tagList) {
            ArticleTag articleTag = new ArticleTag();
            articleTag.setTagId(Long.parseLong(tag.getId()));
            articleTag.setArticleId(article.getId());
            articleTagMapper.insert(articleTag);
        }
        ArticleRep articleRep = new ArticleRep();
        articleRep.setId(String.valueOf(article.getId()));
        return articleRep;
    }

    @Override
    public List<Article> listArticle(PageParams pageParams) {
        Page<Article> page = PageUtil.setPageParams(pageParams);
        IPage<Article> articlePage = articleMapper.listArticle(page, pageParams.getCategoryId(),
                pageParams.getTagId(), pageParams.getYear(), pageParams.getMonth());
        return articlePage.getRecords();
    }

    @Override
    public List<Article> listUserArticle(PageParams pageParams, Long userId) {
        QueryWrapper<Article> queryWrapper = new QueryWrapper<>();
        queryWrapper.lambda()
                .eq(CheckUtil.isNotNull(userId), Article::getAuthorId, userId)
                .orderByDesc(Article::getCreateTime);

        return PageUtil.getPageList(pageParams, articleMapper.selectList(queryWrapper));
    }

    @Override
    public Article findArticleById(Long articleId) {
        QueryWrapper<Article> queryWrapper = new QueryWrapper<>();
        queryWrapper.lambda().eq(CheckUtil.isNotNull(articleId), Article::getId, articleId);
        return articleMapper.selectOne(queryWrapper);
    }

    @Override
    public int refreshNewArticle() {
        UpdateWrapper<Article> updateWrapper = new UpdateWrapper<>();
        updateWrapper.lambda().eq(Article::getWeight, Constant.ARTICLE_NEW)
                .set(Article::getWeight, Constant.ARTICLE_COMMON)
                .le(Article::getCreateTime, LocalDateTime.now());

        return articleMapper.update(null, updateWrapper);
    }

    @Override
    public List<Archives> listArchives() {
        return articleMapper.listArchives();
    }
}
